﻿using System;
using System.Collections;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.ComponentModel;
using System.ComponentModel.DataAnnotations;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Threading.Tasks;
using MergeTool.ClassLib.Configuration;
using MergeTool.UI.Helpers;

namespace MergeTool.UI.ViewModels
{
    public class MergingSettingsViewModel : MyCustomViewModelBase
    {
        public MergingSettingsViewModel()
        {
            this._mergeSettings = Settings.GetInstance();
            IsAutomaticVersionIncrease = _mergeSettings.IsAutomaticVersionIncrease;
            SpecialVersioningBranch = _mergeSettings.SpecialVersioningBranch;
            BeyondComparePath = _mergeSettings.BeyondComparePath;
            DefaultBranchCheckinCommentPattern = _mergeSettings.DefaultBranchCheckinCommentPattern;
            DefaultChangesetCheckinCommentPattern = _mergeSettings.DefaultChangesetCheckinCommentPattern;
            BranchNameOnlyInComments = _mergeSettings.BranchNameOnlyInComments;
            DefaultWorkItemAssociation = _mergeSettings.DefaultWorkItemAssociation;
            IsKeepMergeHistoryInComments = _mergeSettings.IsKeepMergeHistoryInComments;
            IsAlwaysShowCheckinConfirmation = _mergeSettings.IsAlwaysShowCheckinConfirmation;
        }

        private readonly Settings _mergeSettings;

        private DefaultWorkItemAssociation _defaultWorkItemAssociation;

        public DefaultWorkItemAssociation DefaultWorkItemAssociation
        {
            get { return this._defaultWorkItemAssociation; }
            set
            {
                SetProperty(ref _defaultWorkItemAssociation, value);
                _mergeSettings.DefaultWorkItemAssociation = value;
            }
        }

        private bool _branchNameOnlyInComments;

        public bool BranchNameOnlyInComments
        {
            get { return this._branchNameOnlyInComments; }
            set
            {
                SetProperty(ref _branchNameOnlyInComments, value);
                _mergeSettings.BranchNameOnlyInComments = value;
            }
        }

        public string TempWorkspacePath
        {
            get { return this._mergeSettings.TempWorkspacePath; }
            set
            {
                string tempWorkspacePath = _mergeSettings.TempWorkspacePath;
                SetProperty(ref tempWorkspacePath, value);
                _mergeSettings.TempWorkspacePath = value;
            }
        }

        private string _defaultChangesetCheckinCommentPattern;

        public string DefaultChangesetCheckinCommentPattern
        {
            get { return this._defaultChangesetCheckinCommentPattern; }
            set
            {
                SetProperty(ref _defaultChangesetCheckinCommentPattern, value);
                _mergeSettings.DefaultChangesetCheckinCommentPattern = value;
            }
        }
        
        private bool _isAlwaysShowCheckinConfirmation;

        public bool IsAlwaysShowCheckinConfirmation
        {
            get { return this._isAlwaysShowCheckinConfirmation; }
            set
            {
                SetProperty(ref _isAlwaysShowCheckinConfirmation, value);
                _mergeSettings.IsAlwaysShowCheckinConfirmation = value;
            }
        }


        public string DefaultBranchCheckinCommentPattern
        {
            get { return this._defaultBranchCheckinCommentPattern; }
            set
            {
                SetProperty(ref _defaultBranchCheckinCommentPattern, value);
                _mergeSettings.DefaultBranchCheckinCommentPattern = value;
            }
        }
        private string _defaultBranchCheckinCommentPattern;

        public string BeyondComparePath
        {
            get { return this._beyondComparePath; }
            set
            {
                SetProperty(ref _beyondComparePath, value);
                _mergeSettings.BeyondComparePath = value;
            }
        }

        private string _beyondComparePath;


        public bool IsUsingCabFeatures
        {
            get { return _mergeSettings.IsUsingCabFeatures; }
        }

        public bool IsAutomaticVersionIncrease
        {
            get { return this._isAutomaticVersionIncrease; }
            set
            {
                SetProperty(ref _isAutomaticVersionIncrease, value);
                _mergeSettings.IsAutomaticVersionIncrease = value;
            }
        }

        private bool _isAutomaticVersionIncrease;

        public bool IsKeepMergeHistoryInComments
        {
            get { return this._isKeepMergeHistoryInComments; }
            set
            {
                SetProperty(ref _isKeepMergeHistoryInComments, value);
                _mergeSettings.IsKeepMergeHistoryInComments = value;
            }
        }

        private bool _isKeepMergeHistoryInComments;
        
        private string _specialVersioningBranch;

        public string SpecialVersioningBranch
        {
            get { return this._specialVersioningBranch; }

            set
            {
                SetProperty(ref _specialVersioningBranch, value);
                _mergeSettings.SpecialVersioningBranch = value;
            }
        }

        public int DefaultWorkItemToAssociate
        {
            get { return this._mergeSettings.DefaultWorkItemToAssociate; }
            set
            {
                int defaultWorkItemToAssociate = _mergeSettings.DefaultWorkItemToAssociate;
                ValidateWorkItem(value);
                SetProperty(ref defaultWorkItemToAssociate, value);
                _mergeSettings.DefaultWorkItemToAssociate = value;
            }
        }

        private async void ValidateWorkItem(int workItemId)
        {
            const string propertyName = "DefaultWorkItemToAssociate";
            

            var results = new List<ValidationResult>();
            var witValidator = new WorkItemValidator();

            bool isValid = await Task.Run(() =>
            {
                return witValidator.ValidateWit(results, workItemId);
            })
            .ConfigureAwait(false);

            if (!isValid)
            {
                this.ErrorsContainer.SetErrors(propertyName, new List<ValidationResult>()
                {
                    new ValidationResult(results[0].ErrorMessage)
                });
                RaiseErrorsChanged(propertyName);
            }
            else
            {
                this.ErrorsContainer.ClearErrors(propertyName);
                RaiseErrorsChanged(propertyName);
            }
        }
    }
}
